#!/usr/bin/env python3

import time
import backtrader as bt
import datetime as dt
import baostock as bs
import pandas as pd
import tushare as ts
from decimal import Decimal
import math
import numpy as np
import datetime
import matplotlib.pyplot as plt
#from ccxtbt import CCXTStore
from config import BINANCE, ENV, PRODUCTION, COIN_TARGET, COIN_REFER, DEBUG

from dataset.dataset import CustomDataset
from sizer.percent import FullMoney
from strategies.AlphaPortfolioStrategy import AlphaPortfolioStrategy
from strategies.SsaStrategy import SsaStrategy
from strategies.TestStrategy import TestStrategy
from strategies.base import StrategyBase
from strategies.basic_rsi import BasicRSI
from strategies.boll import Boll
from utils import print_trade_analysis, print_sqn, send_telegram_message

# 统计回测周期内K线数量
def bar_size(df, fromdate, todate):
    #df = pd.read_csv(datapath)
    return len(df[(df['date'] >= fromdate.strftime('%Y-%m-%d'))
            & (df['date'] <= todate.strftime('%Y-%m-%d'))])


def main():
    cerebro = bt.Cerebro(quicknotify=True)
    lg = bs.login(user_id='anonymous', password='123456')
    data = '2015-01-01'
    rs = bs.query_history_k_data_plus("sh.600163",
                                      "date,code,open,high,low,close,preclose,volume,amount,adjustflag,turn,tradestatus,pctChg,peTTM,pbMRQ,psTTM,pcfNcfTTM,isST",
                                      start_date=data, end_date='%s-%s-%s' % (
            datetime.datetime.now().year, datetime.datetime.now().month, datetime.datetime.now().day),
                                      frequency="d",
                                      adjustflag="2")

    df_init = []
    result_list = []
    while (rs.error_code == '0') & rs.next():
        # 获取一条记录，将记录合并在一起
        d = rs.get_row_data()
        result_list.append(d)
        df_init = pd.DataFrame(result_list, columns=rs.fields)

    df_init = df_init.astype({'volume':'float','high': 'float', 'open': 'float', 'close': 'float', 'low': 'float'})
    df_init.date = pd.to_datetime(df_init.date)
    data = bt.feeds.PandasData(dataname=df_init,
                                                          #datetime=0,
                                                          datetime='date',
                                                          openinterest=-1,
                                                          open='open',
                                                          high='high',
                                                          low='low',
                                                          close='close',
                                                          volume='volume',
                                                          fromdate=datetime.datetime(2015, 1, 1),
                                                          todate=datetime.datetime(2021, 12, 16))

    """
    pro = ts.pro_api(token='936d1029be68a59a3e77eeb9e4eb1ea3c36502bd4b4bf9e1aae91bd8')
    df = pro.daily(ts_code='000001.SZ', start_date='20110101', end_date='20210101').iloc[::-1]
    df.trade_date = pd.to_datetime(df.trade_date)  # 由于trade_date是字符串，BackTrader无法识别，需要转一下

    data = bt.feeds.PandasData(
        dataname=df1.get_data(),
        fromdate=datetime.datetime(2011, 1, 1),
        todate=datetime.datetime(2012, 12, 31),
        datetime='trade_date',
        open='open',
        high='high',
        low='low',
        close='close',
        volume='vol',
        openinterest=-1
    )

    """

    #df = df[['open', 'high', 'low', 'close', 'volume']]

    #data = bt.feeds.PandasData(dataname=df,
    #                           fromdate=datetime(2015, 1, 1),
    #                           todate=datetime(2020, 4, 17))

    #data.to_csv('D:\\3007.csv', columns=['date','open','high','low','close','volume'])

    #dataframe = pd.read_csv('D:\\3006.csv', index_col=0, parse_dates=True)

    #dataframe['openinterest'] = 0

    #data = bt.feeds.PandasData(dataname= df.get_data(),
    #                           #datetime=0,
    #                           open=1,
    #                           high=2,
    #                           low=3,
    #                           close=4,
    #                           fromdate=datetime.datetime(2015, 1, 1),
    #                           todate=datetime.datetime(2021, 12, 16))






    cerebro.resampledata(data, timeframe=bt.TimeFrame.Minutes, compression=30)

    broker = cerebro.getbroker()

    broker.setcommission(commission=0.001, name=COIN_TARGET)  # 佣金
    broker.setcash(100000.0) #

    cerebro.addsizer(FullMoney) #设定需要设定每次交易买入的股数
    #cerebro.addsizer(bt.sizers.FixedSize, stake=100)

    # Analyzers to evaluate trades and strategies
    # SQN = Average( profit / risk ) / StdDev( profit / risk ) x SquareRoot( number of trades )
    cerebro.addanalyzer(bt.analyzers.TradeAnalyzer, _name="ta")
    cerebro.addanalyzer(bt.analyzers.SQN, _name="sqn")

    # Include Strategy
    cerebro.addstrategy(SsaStrategy)

    # Starting backtrader bot
    initial_value = cerebro.broker.getvalue()
    print('Starting Portfolio Value: %.2f' % initial_value)
    result = cerebro.run()

    # Print analyzers - results
    final_value = cerebro.broker.getvalue()
    print('Final Portfolio Value: %.2f' % final_value)
    print('Profit %.3f%%' % ((final_value - initial_value) / initial_value * 100))
    try :
       # 性能输出：
       print('夏普率:', result[0].analyzers.mysharpe.get_analysis())
       print_trade_analysis(result[0].analyzers.ta.get_analysis())
       print_sqn(result[0].analyzers.sqn.get_analysis())

    except Exception as e:
        1 + 1
    finally:
        cerebro.plot()
    #if DEBUG:



if __name__ == "__main__":
    try:
        main()
    except KeyboardInterrupt:
        print("finished.")
        time = dt.datetime.now().strftime("%d-%m-%y %H:%M")
        send_telegram_message("Bot finished by user at %s" % time)
    except Exception as err:
        send_telegram_message("Bot finished with error: %s" % err)
        print("Finished with error: ", err)
        raise